// @strict-types

#Область ОбработчикиСобытийФормы

&НаСервере
Процедура ПриСозданииНаСервере(Отказ, СтандартнаяОбработка)

	ЗаполнитьЗаголовокИзПараметров();
	
	ЗаполнитьСписокВыбораТипаКоллекции();
	
	ЗаполнитьДеревоПриСозданииФормы();
	
КонецПроцедуры

&НаКлиенте
Процедура ПриОткрытии(Отказ)
	
	КорневыеЭлементы = РедактируемоеЗначение.ПолучитьЭлементы();
	Если ЗначениеЗаполнено(КорневыеЭлементы) Тогда
		Элементы.РедактируемоеЗначение.Развернуть(КорневыеЭлементы[0].ПолучитьИдентификатор(), Ложь);
	КонецЕсли;
	
КонецПроцедуры

#КонецОбласти

#Область ОбработчикиСобытийЭлементовТаблицыФормыРедактируемоеЗначение

&НаКлиенте
Процедура РедактируемоеЗначениеПередНачаломДобавления(Элемент, Отказ, Копирование, Родитель, Группа, Параметр)
	
	ТекущиеДанные = Элементы.РедактируемоеЗначение.ТекущиеДанные;
	Если ТекущиеДанные = Неопределено Тогда
		Отказ = Истина;
	Иначе
		ТекущийРодитель = ТекущиеДанные.ПолучитьРодителя();
		Если Копирование И ТекущийРодитель = Неопределено Тогда
			Отказ = Истина;
		ИначеЕсли ПустаяСтрока(ТекущиеДанные.ТипКоллекции) Тогда
			Отказ = Истина;
		КонецЕсли;
	КонецЕсли;
		
КонецПроцедуры

&НаКлиенте
Процедура РедактируемоеЗначениеПриАктивизацииСтроки(Элемент)
	
    ТекущиеДанные = Элементы.РедактируемоеЗначение.ТекущиеДанные; // см. ОписаниеСтрокиДерева
	Если ТекущиеДанные = Неопределено Тогда
		Возврат;
	КонецЕсли;
	
	Родитель = ТекущиеДанные.ПолучитьРодителя();
	Если Родитель = Неопределено Тогда
		Возврат;
	КонецЕсли;
	
	Если СтрЗаканчиваетсяНа(Родитель.ТипКоллекции, "Структура") Тогда
		Элементы.РедактируемоеЗначениеКлюч.ВыбиратьТип = Ложь;
		ТекущиеДанные.Ключ = Строка(ТекущиеДанные.Ключ);
	Иначе
		Элементы.РедактируемоеЗначениеКлюч.ВыбиратьТип = Истина;
	КонецЕсли;
	
КонецПроцедуры

#КонецОбласти

#Область ОбработчикиКомандФормы

&НаКлиенте
Процедура ПрименитьИзменения(Команда)
	
	ОписаниеКорня      = РедактируемоеЗначение.ПолучитьЭлементы()[0];
	
	ПолученноеЗначение = НоваяКоллекция(ОписаниеКорня.ТипКоллекции);
	
	ЗаполнитьРезультат(ОписаниеКорня, ПолученноеЗначение);
	
	ПолученноеЗначение = ЗапечататьФиксированнуюКоллекцию(ПолученноеЗначение, ОписаниеКорня.ТипКоллекции);
	
	Закрыть(Новый Структура("ЗначениеРеквизита", ПолученноеЗначение));
	
КонецПроцедуры

#КонецОбласти

#Область СлужебныеПроцедурыИФункции

#Область ИнициализацияФормы

&НаСервере
Процедура ЗаполнитьЗаголовокИзПараметров()
	
	Если ЗначениеЗаполнено(Параметры.Заголовок) Тогда
		Заголовок = Параметры.Заголовок;
		АвтоЗаголовок = Ложь;
	КонецЕсли;
	
КонецПроцедуры

&НаСервере
Процедура ЗаполнитьСписокВыбораТипаКоллекции()
	
	СписокВыбора = Элементы.РедактируемоеЗначениеТипКоллекции.СписокВыбора; // СписокЗначений из Строка
	СписокВыбора.Добавить("", "");
	Для Каждого ДоступныйТип Из ДоступныеТипыКоллекций() Цикл
		СписокВыбора.Добавить(ДоступныйТип, ДоступныйТип);
	КонецЦикла;
	
КонецПроцедуры

&НаСервере
Процедура ЗаполнитьДеревоПриСозданииФормы()
	
	//@skip-check property-return-type
	ЗначениеИзПараметров = Параметры.РедактируемоеЗначение; //Произвольный
	
	ОписаниеКорня = РедактируемоеЗначение.ПолучитьЭлементы().Добавить();
	ОписаниеКорня.ТипКоллекции = ТипКоллекции(ЗначениеИзПараметров);
	
	ЗаполнитьДеревоИзСтруктурыСоответствия(ЗначениеИзПараметров, ОписаниеКорня);
	
КонецПроцедуры

#КонецОбласти

// Заполнить результат.
// 
// Параметры:
//  ИсходнаяКоллеция - ДанныеФормыЭлементДерева - Исходная коллеция
//  ЗаполняемоеЗначение - Соответствие из КлючИЗначение, Структура - :
//  * Ключ - Произвольный
//  * Значение - Произвольный
&НаКлиенте
Процедура ЗаполнитьРезультат(ИсходнаяКоллеция, ЗаполняемоеЗначение)
	
	Для Каждого ОписаниеЗначения Из ИсходнаяКоллеция.ПолучитьЭлементы() Цикл // см. ОписаниеСтрокиДерева
		
		Если ЗначениеЗаполнено(ОписаниеЗначения.ТипКоллекции) Тогда
			ТекущееЗначение = НоваяКоллекция(ОписаниеЗначения.ТипКоллекции);
			ЗаполнитьРезультат(ОписаниеЗначения, ТекущееЗначение);
			ТекущееЗначение = ЗапечататьФиксированнуюКоллекцию(ТекущееЗначение, ОписаниеЗначения.ТипКоллекции);
		Иначе
			//@skip-check statement-type-change
			ТекущееЗначение = ОписаниеЗначения.Значение;
		КонецЕсли;
		
		ЗаполняемоеЗначение.Вставить(ОписаниеЗначения.Ключ, ТекущееЗначение);
		
	КонецЦикла;
		
КонецПроцедуры

&НаКлиентеНаСервереБезКонтекста	
Функция ТипКоллекции(Коллекция)
	
	ТипКоллекции = ТипЗнч(Коллекция);
	
	Для Каждого ИмяТипа Из ДоступныеТипыКоллекций() Цикл
		Если ТипКоллекции = Тип(ИмяТипа) Тогда
			Возврат ИмяТипа;
		КонецЕсли;
	КонецЦикла;
	
КонецФункции
	
&НаКлиентеНаСервереБезКонтекста
Функция ДоступныеТипыКоллекций()
	
	Возврат СтрРазделить("Структура,Соответствие,ФиксированнаяСтруктура,ФиксированноеСоответствие", ",");
	
КонецФункции

&НаКлиентеНаСервереБезКонтекста
Функция НоваяКоллекция(ТипКоллекции)
	
	Если СтрЗаканчиваетсяНа(ТипКоллекции, "Структура") Тогда
		Возврат Новый Структура;
	Иначе
		Возврат Новый Соответствие;
	КонецЕсли;
	
КонецФункции

&НаКлиентеНаСервереБезКонтекста
Функция ЗапечататьФиксированнуюКоллекцию(Коллекция, ТипКоллекции)
	
	Если НЕ СтрНачинаетсяС(ТипКоллекции, "Фикс") Тогда
		Возврат Коллекция;
	ИначеЕсли ТипЗнч(Коллекция) = Тип("Структура") Тогда
		Возврат Новый ФиксированнаяСтруктура(Коллекция);
	Иначе
		Возврат Новый ФиксированноеСоответствие(Коллекция);
	КонецЕсли;
	
КонецФункции
 
&НаСервере
Процедура ЗаполнитьДеревоИзСтруктурыСоответствия(ТекущееЗначение, ТекущийРодитель)
	
	КоллекцияСтрок = ТекущийРодитель.ПолучитьЭлементы();
	Для Каждого КлючИЗначение Из ТекущееЗначение Цикл // см. ОписаниеСтрокиДерева
		
		ОписаниеСтроки = КоллекцияСтрок.Добавить(); // см. ОписаниеСтрокиДерева
		ОписаниеСтроки.Ключ = КлючИЗначение.Ключ;
		
		ТекущееЗначение = КлючИЗначение.Значение; // Произвольный
		ОписаниеСтроки.ТипКоллекции = ТипКоллекции(ТекущееЗначение);
		
		Если ЗначениеЗаполнено(ОписаниеСтроки.ТипКоллекции) Тогда
			ЗаполнитьДеревоИзСтруктурыСоответствия(ТекущееЗначение, ОписаниеСтроки);
		Иначе
			ОписаниеСтроки.Значение = ТекущееЗначение;
		КонецЕсли;
		
	КонецЦикла;
	
КонецПроцедуры

// Описание строки дерева.
// @skip-check module-unused-method
// 
// Возвращаемое значение:
//  ДанныеФормыЭлементДерева:
//  * Ключ - Произвольный
//  * Значение - Произвольный
//  * ТипКоллекции - Строка
&НаКлиентеНаСервереБезКонтекста
Функция ОписаниеСтрокиДерева()
	
	Возврат Новый Структура;
	
КонецФункции

#КонецОбласти
